package cn.lightpm.controller.account;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.mvc.multiaction.MultiActionController;
import org.springframework.web.servlet.view.RedirectView;

import cn.lightpm.dao.HibernateUtils;
import cn.lightpm.entity.account.Authority;
import cn.lightpm.entity.account.Role;
import cn.lightpm.service.account.AccountManager;
import cn.lightpm.util.web.OptionalItem;
import cn.lightpm.util.web.SiteDefs;

@Controller
@RequestMapping("/role")
public class RoleController extends MultiActionController {
	@Autowired
	private AccountManager accountManager;

	/** 列表 */
	@RequestMapping(method = RequestMethod.GET)
	public ModelAndView index() {
		List<Role> roles = accountManager.getAllRole();
		return new ModelAndView("/account/role", "roles", roles);
	}

	/** 显示 */
	@RequestMapping(value = "/{id}", method = RequestMethod.GET)
	public ModelAndView show(@PathVariable Long id) throws Exception {
		Role role = accountManager.getRole(id);
		return new ModelAndView("/account/role-input", "role", role);
	}

	/** 进入新增 */
	@RequestMapping(value = "/new")
	public ModelAndView _new() throws Exception {
		Role role = new Role();
		return new ModelAndView("/account/role-input", createModelForViewer(role));
	}

	/** 进入编辑 */
	@RequestMapping(value = "/{id}/edit")
	public ModelAndView edit(@PathVariable Long id) throws Exception {
		Role role = accountManager.getRole(id);
		return new ModelAndView("/account/role-input", createModelForViewer(role));
	}

	/** 保存新增 */
	@RequestMapping(value = "/new", method = RequestMethod.POST)
	public ModelAndView create(Role role, Long[] checkedAuthorityIds) {
		saveRole(role, checkedAuthorityIds);
		return new ModelAndView(new RedirectView(SiteDefs.CONTEXT_NAME + "/role"));
	}

	/** 保存更新 */
	@RequestMapping(value = "/{id}", method = RequestMethod.PUT)
	public ModelAndView update(Role role, Long[] checkedAuthorityIds) {
		saveRole(role, checkedAuthorityIds);
		return new ModelAndView(new RedirectView(SiteDefs.CONTEXT_NAME + "/role"));
	}

	/** 删除 */
	@RequestMapping(value = "/{id}", method = RequestMethod.DELETE)
	public ModelAndView delete(@PathVariable Long id) {
		accountManager.deleteRole(id);
		return new ModelAndView("/account/role");
	}

	/** 构造用于视图展现的Model数据 */
	private Map<String, Object> createModelForViewer(Role role) {
		Map<String, Object> model = new HashMap<String, Object>();
		model.put("role", role);
		model.put("optionalAuthorities", createOptionalItemsForAuthority(role));
		return model;
	}

	/** 构造授权的选项列表 */
	private List<OptionalItem> createOptionalItemsForAuthority(Role role) {
		List<OptionalItem> items = new ArrayList<OptionalItem>();
		List<Authority> selectedAuthorities = role.getAuthorityList();
		List<Authority> allAuthorities = accountManager.getAllAuthority();
		for (Authority authority : allAuthorities) {
			OptionalItem item = new OptionalItem(authority.getId(), authority.getName());
			item.setSelected(selectedAuthorities.contains(authority));
			items.add(item);
		}
		return items;
	}

	/** 保存角色信息和相关的授权列表 */
	private void saveRole(Role role, Long[] checkedAuthorityIds) {
		if (checkedAuthorityIds == null) {
			checkedAuthorityIds = new Long[0];
		}
		HibernateUtils.mergeByCheckedIds(role.getAuthorityList(), Arrays.asList(checkedAuthorityIds), Authority.class);
		accountManager.saveRole(role);

	}

}
